//
//  QGComposeTypeView.swift
//  斯威夫特微博
//
//  Created by youyoumacmini3 on 2017/7/31.
//  Copyright © 2017年 youyoumacmini3. All rights reserved.
//

import UIKit
import pop

class QGComposeTypeView: UIView {

    
    @IBOutlet weak var scrollView: UIScrollView!
    // 关闭按钮约束
    @IBOutlet weak var closeButtonCenterXCons: NSLayoutConstraint!
    // 返回前一页按钮约束
    @IBOutlet weak var backButtonCenterXCons: NSLayoutConstraint!
    // 返回前一页按钮
    @IBOutlet weak var backButton: UIButton!
    
    /// 按钮数据数组
    fileprivate let buttonsInfo = [["imageName": "tabbar_compose_idea", "title": "文字", "clsName": "QGComposeViewController"],
                               ["imageName": "tabbar_compose_photo", "title": "照片/视频"],
                               ["imageName": "tabbar_compose_weibo", "title": "长微博"],
                               ["imageName": "tabbar_compose_lbs", "title": "签到"],
                               ["imageName": "tabbar_compose_review", "title": "点评"],
                               ["imageName": "tabbar_compose_more", "title": "更多", "actionName": "clickMore"],
                               ["imageName": "tabbar_compose_friend", "title": "好友圈"],
                               ["imageName": "tabbar_compose_wbcamera", "title": "微博相机"],
                               ["imageName": "tabbar_compose_music", "title": "音乐"],
                               ["imageName": "tabbar_compose_shooting", "title": "拍摄"]]
    
    // 完成回调
    private var completionBlock: ((_ clsName: String?)->())?
    
    //MARK: - 实例化方法
    class func comPoseTypeView() -> QGComposeTypeView {
        
        let nib = UINib(nibName: "QGComposeTypeView", bundle: nil)
        
        // 从 xib 加载完成视图，就会调用 awakeFromNib,如果此处在awakeFromNib中调用 setUI()，则下面frame的代码设置不到，导致view的 frame有问题，跟着后面scrollView布局都会有问题。所以改在此处下面调用setUI
        let v = nib.instantiate(withOwner: nil, options: nil)[0] as! QGComposeTypeView
        
        // xib 加载默认大小 600 * 600 - 此处需要放在setUI上面，不然只能拿到xib中的 frame 不能拿到实际操作设备的frame
        v.frame = UIScreen.main.bounds
        
        v.setUI()
        
        return v
    }

    // 显示当前视图
    // OC中的 block 如果当前方法不能执行，通常使用属性记录，在需要的时候执行
    func show(completion: @escaping (_ clsName: String?)->()) {
        
        // 0. 记录闭包
        completionBlock = completion
        
        // 1. 将当前视图添加到 根视图控制器 的 view
        guard let vc = UIApplication.shared.keyWindow?.rootViewController else { return }
        
        // 2. 添加视图
        vc.view.addSubview(self)
        
        // 3. 开始动画
        showCurrentView()
    }
    

    
    // MARK: - 监听方法
    @objc fileprivate func clickBtn(selectedButton: QGComposeTypeButton) {
  
        // 1. 判断当前显示的视图(即scrollView上的哪个view)
        let page = Int(scrollView.contentOffset.x / scrollView.bounds.width)
        let v = scrollView.subviews[page]
        
        // 2. 遍历当前视图 - 为选中的按钮放大，其他按钮缩小
        for (i,btn) in v.subviews.enumerated() {
            
            // 1. 缩放动画
            let scaleAnim: POPBasicAnimation = POPBasicAnimation(propertyNamed: kPOPViewScaleXY)
            
            // X,Y 在系统中使用 CGPoint表示，如果要转换成 id，需要使用 ‘NSValue’ 包装
            let scale = (selectedButton == btn) ? 2 : 0.3
            let value = NSValue(cgPoint: CGPoint(x: scale, y: scale))
            
            scaleAnim.toValue = value
            scaleAnim.duration = 0.5
        
            btn.pop_add(scaleAnim, forKey: nil)
            
            // 2. 渐变动画 - 动画组
            let alphaAnim: POPBasicAnimation = POPBasicAnimation(propertyNamed: kPOPViewAlpha)
            alphaAnim.toValue = 0.2
            alphaAnim.duration = 0.5
            
            btn.pop_add(alphaAnim, forKey: nil)
            
          
            // 3. 监听
    
            if i == 0 {
                alphaAnim.completionBlock = { _, _ in
                    // 需要执行回调
                    print("完成毁掉")
                    // 执行完成闭包
                    self.completionBlock?(selectedButton.clsName)
                }
            }
            
        }
        
        
    }
    
    @objc fileprivate func clickMore() {
        print("点击更多")
        // 1. 将 scrollView 滚动到第二页
        let offSet = CGPoint(x: scrollView.bounds.width, y: 0)
        scrollView.setContentOffset(offSet, animated: true)
        
        // 2. 处理底部按钮，让两个按钮分开显示
        backButton.isHidden = false
        let margin = scrollView.bounds.width / 6
        closeButtonCenterXCons.constant += margin
        backButtonCenterXCons.constant -= margin
        
        UIView.animate(withDuration: 0.25) { 
            self.layoutIfNeeded()
        }
        
    }
    
    @IBAction func clickBack() {
        // 将滚动视图 滚动到第一页
        scrollView.setContentOffset(CGPoint(x: 0, y: 0), animated: true)
        // 按钮合并

        closeButtonCenterXCons.constant = 0
        backButtonCenterXCons.constant = 0
        
        UIView.animate(withDuration: 0.25, animations: { 
            self.layoutIfNeeded()
            self.backButton.alpha = 0
        }) { (_) in
            self.backButton.isHidden = true
            self.backButton.alpha = 1
        }
    }
    
    @IBAction func close() {
        hideButtons()
    }
}

// MARK: - 弹出按钮滑动代理方法
extension QGComposeTypeView: UIScrollViewDelegate {
    
    func scrollViewDidEndDecelerating(_ scrollView: UIScrollView) {
        let page = Int(scrollView.contentOffset.x / scrollView.bounds.width)
        print(page)
        if page == 0 {
            clickBack()
        }else if page == 1{
            if closeButtonCenterXCons.constant == 0 {
                clickMore()
            }
        }
    }
}


// MARK: - 动画方法扩展
private extension QGComposeTypeView {
    
    //MARK: - 消除部分的动画
    /// 隐藏按钮动画
    func hideButtons() {
        // 1. 根据 contentOffSet 判断当前显示的子视图
        let page = Int(scrollView.contentOffset.x / scrollView.bounds.width)
        let v = scrollView.subviews[page]
        
        // 2. 遍历 v 中的所有按钮
        for (i,btn) in v.subviews.enumerated().reversed() {
            
            // a. 创建动画
            let anim:POPSpringAnimation = POPSpringAnimation(propertyNamed: kPOPLayerPositionY)
            
            // b. 设置动画属性
            anim.fromValue = btn.center.y
            anim.toValue = v.bounds.width
            
            // 设置时间
            anim.beginTime = CACurrentMediaTime() + CFTimeInterval(v.subviews.count - i) * 0.025
            
            // c. 添加动画
            btn.layer.pop_add(anim, forKey: nil)
            
            // d. 监听第0个按钮动画 - 是最后一个执行的
            if i == 0 {
                anim.completionBlock = {_, _ in
                    
                    self.hideCurrentView()
                }
            }
        }
    }
    
    // 隐藏当前视图 - 开始时间
    func hideCurrentView() {
        // 1. 创建动画
        let anim: POPBasicAnimation = POPBasicAnimation(propertyNamed: kPOPViewAlpha)
        anim.fromValue = 1
        anim.toValue = 0
        anim.duration = 0.25
        
        // 2. 添加到视图
        pop_add(anim, forKey: nil)
        
        // 3. 添加完成监听方法
        anim.completionBlock = {_, _ in
            self.removeFromSuperview()
        }
    }
    
    //MARK: - 显示部分的动画
    /// 动画显示当前视图
    func showCurrentView() {
        // 1. 创建动画
        let anim: POPBasicAnimation = POPBasicAnimation(propertyNamed: kPOPViewAlpha)
        anim.fromValue = 0
        anim.toValue = 1
        anim.duration = 0.25
        // 2. 添加到视图
        pop_add(anim, forKey: nil)
        
        // 3. 添加按钮动画
        showButtons()
    }
    
    
    /// 弹力显示所有按钮
    func showButtons() {
        // 1. 获取 scrollView 的子视图的第0个视图
        let v = scrollView.subviews[0]
        
        // 2. 遍历 v 中的所有按钮
        for (i,btn) in v.subviews.enumerated() {
            // a. 创建动画
            let anim:POPSpringAnimation = POPSpringAnimation(propertyNamed: kPOPLayerPositionY)
            // b. 设置动画属性
            anim.fromValue = self.bounds.width
            anim.toValue = btn.center.y
            
             // 更多方法不清楚都可以点击去找
            // 弹力系数 - 取值范围 0~20 数值越大，弹性越大，默认为4
            anim.springBounciness = 10
            // 弹力速度 - 取值范围 0~20 数值越大，速度越大，默认为12
            anim.springSpeed = 10
            
            // 设置启动时间
            anim.beginTime = CACurrentMediaTime() + CFTimeInterval(i) * 0.025
            
            // 添加动画
            btn.pop_add(anim, forKey: nil)
        }
    }
    
}

// MARK: - 界面
// private 让 extension 中多有的方法都是私有
private extension QGComposeTypeView {
    func setUI() {
        
        // 0. 强行更新布局
        layoutIfNeeded()
        
        // 1. 向 scrollView 添加视图
        let rect = scrollView.bounds

        let width = scrollView.bounds.width
        
        for i in 0..<2 {
            let v = UIView(frame: rect.offsetBy(dx: CGFloat(i) * width, dy: 0))
            
            // 2. 向视图添加按钮
            addButtons(v: v, idx: i * 6)
            
            // 3. 将试图添加到 scrollView
            scrollView.addSubview(v)
        }
        
        // 设置 scrollView
        scrollView.contentSize = CGSize(width: 2 * width, height: 0)
        scrollView.showsVerticalScrollIndicator = false
        scrollView.showsHorizontalScrollIndicator = false
        scrollView.bounces = false
        scrollView.isPagingEnabled = true
        scrollView.delegate = self
        // 禁用滚动
        //scrollView.isScrollEnabled = false
    }
    
    
    /// 向v中添加按钮。按钮的数组索引从idx开始
    func addButtons(v: UIView, idx: Int) {
        
        let count = 6
        
        // 从idx 开始添加 6个按钮
        for i in idx..<(idx + count) {
            
            if i >= buttonsInfo.count {
                break
            }
            
            // 0. 从数组字典中获取图像名称 和 title
            let dic = buttonsInfo[i]
            guard let imageName = dic["imageName"],
                  let title = dic["title"] else { continue }
            
            
            // 1. 创建按钮
            let btn = QGComposeTypeButton.composeTypeButton(imageName: imageName, title: title)
            v.addSubview(btn)
            
            // 3. 添加按钮监听方法
            if let actionName = dic["actionName"] {
                // 使用<#T##Selector#> 调用方法
                // OC 中使用 NSSelectorFromString(@"clickMore")
                btn.addTarget(self, action: Selector(actionName), for: .touchUpInside)
            } else {
           
                btn.addTarget(self, action: #selector(clickBtn), for: .touchUpInside)
            }
            // 4. 设置要展现的类名 - 不需要任何判断，有就设置，无就不设置
            btn.clsName = dic["clsName"]
            
        }
        
        // 遍历视图的子视图，布局按钮
        let btnSize = CGSize(width: 100, height: 100)
        let margin = (v.bounds.width - 3 * btnSize.width) / 4
        
        for (i,btn) in v.subviews.enumerated() {
            let y: CGFloat = (i > 2) ? (v.bounds.height - btnSize.height) : 0
            let col = i % 3
            let x = CGFloat(col + 1) * margin + CGFloat(col) * btnSize.width
            btn.frame = CGRect(x: x, y: y, width: btnSize.width, height: btnSize.height)
            
        }
    }
}


